﻿import { layoutComponents, formComponents, otherComponents } from '../data/componentsData'

const getComponent = function (name) {
  let c = formComponents.find(item => {
    return item.componentName === name
  })
  if (!c) {
    c = layoutComponents.find(item => {
      return item.componentName === name
    })
  }
  if (!c) {
    c = otherComponents.find(item => {
      return item.componentName === name
    })
  }
  if (c) {
    return JSON.parse(JSON.stringify(c))
  } else {
    return null
  }
}
const getDataSourceSettings = function () {
  return {
    mode: 'remote',
    remoteCategory: 'MetaPop',
    preview: true,
    DicSettings: {
      table: '',
      valueKey: 'code',
      labelKey: 'value'
    },
    MetaSettings: {
      table: '',
      filterList: [],
      orderList: [],
      valueKey: '',
      labelKey: ''
    },
    MetaPopSettings: {
      table: '',
      orderList: [],
      column: ''
    },
    APISettings: {
      api_uid: '',
      api_url: '',
      input_header: [],
      input_path: [],
      input_querystring: [],
      input_postdata: [],
      dataObject: '',
      valueKey: '',
      labelKey: ''
    },
    staticOptions: []
  }
}
const setComponentConfig4Pop = function (component, column, alltableschema) {
  let refobj = parseRefExpress(column)
  if (!refobj.ref_table) return component
  component.config.other.dataSource.MetaPopSettings.valueKey = refobj.ref_key_column
  component.config.other.dataSource.MetaPopSettings.labelKey = refobj.text
  let refinfo = alltableschema.find(v => {
    return v.name === refobj.ref_table
  })
  if (refinfo) {
    // 表格栏位设定
    if (refobj.show) {
      refobj.show.forEach(s => {
        let cinfo = refinfo.columns.find(c => {
          return c.column_name === s
        })
        if (cinfo) {
          component.config.other.table.columns.push({
            name: cinfo.column_name,
            label: cinfo.column_desc,
            visible: true,
            width: '',
            sort: component.config.other.table.columns.length,
            data_type: cinfo.data_type,
            ui_type: cinfo.ui_type,
            sortable: false,
            sortCustom: false
          })
        }
      })
    } else {
      let cinfo = refinfo.columns.find(c => {
        return c.column_name === refobj.text
      })
      if (cinfo) {
        component.config.other.table.columns.push({
          name: cinfo.column_name,
          label: cinfo.column_desc,
          visible: true,
          width: '',
          sort: component.config.other.table.columns.length,
          data_type: cinfo.data_type,
          ui_type: cinfo.ui_type,
          sortable: false,
          sortCustom: false
        })
      }
    }
  }
  return component
}
export function getComponentNameByUIType (ui_type) {
  let rtn = 'TextInput'
  switch (ui_type) {
    case 'Select':
      rtn = 'SelectInput'
      break
    case 'Switch':
      rtn = 'SwitchInput'
      break
    case 'MultiSelect':
      rtn = 'SelectInput[Multi]'
      break
    case 'RadioButton':
      rtn = 'RadioInput'
      break
    case 'CalendarDate':
      rtn = 'DatePicker'
      break
    case 'Calendar':
      rtn = 'DateTimePicker'
      break
    case 'CalendarYear':
      rtn = 'YearPicker'
      break
    case 'CalendarYearMonth':
      rtn = 'MonthPicker'
      break
    case 'IntInput':
      rtn = 'NumberInput'
      break
    case 'Money':
      rtn = 'NumberInput'
      break
    case 'DecimalInput':
      rtn = 'NumberInput'
      break
    case 'TextArea':
      rtn = 'TextInput[TextArea]'
      break
    case 'EmailInput':
      rtn = 'TextInput[Email]'
      break
    case 'MobileInput':
      rtn = 'TextInput[Mobile]'
      break
    case 'MACInput':
      rtn = 'TextInput[MAC]'
      break
    case 'IDInput':
      rtn = 'TextInput[ID]'
      break
    case 'Picture':
      rtn = 'PictureUpload'
      break
    case 'Pictures':
      rtn = 'PicturesUpload'
      break
    case 'File':
      rtn = 'FileUpload'
      break
    case 'Files':
      rtn = 'FilesUpload'
      break
    case 'Pop':
      rtn = 'PopInput'
      break
    case 'MultiPop':
      rtn = 'PopInput[Multi]'
      break
    case 'MapXY':
      rtn = 'MapInput'
      break
    case 'MD':
      rtn = 'MDInput'
      break
    default:
      break
  }
  return rtn
}
/**
 * 解析引用表达式
 * @param {object} column 元数据栏位信息
 * @returns object
 */
export function parseRefExpress (column) {
  let rtn = {
    ref_table: '',
    ref_key_column: '',
    show: [],
    text: ''
  }
  if (!column) return rtn
  let ref_express = column.reference
  if (!ref_express) return rtn
  let refobj = JSON.parse(ref_express)
  if (!refobj) return rtn
  rtn.ref_table = refobj['$ref_table']
  rtn.ref_key_column = refobj['$ref_key_column']
  rtn.show = refobj['$show']
  rtn.text = refobj['$text']
  return rtn
}
/**
 * 根据组件名称获取组件信息
 * @param {string} name 组件名称
 * @returns 组件setting
 */
export function getComponentByName (name) {
  let rtn = getComponent(name)
  rtn.config.uid = Date.parse(new Date()) + '_' + Math.ceil(Math.random() * 999999)
  rtn.config.dataKey = rtn.type + '_' + rtn.config.uid
  return rtn
}
/**
 * 根据元数据栏位信息生成对应的组件配置信息
 * @param {object} column 元数据栏位信息对象
 * @param {string} meta_uid 元数据uid
 * @param {Array} alltableschema 所有的元数据和词典表的schema信息列表
 * @returns {
 *  componentName: '组件名称',
 *  config: '组件配置信息'
 * }
 */
export function getComponentByMetaColumnInfo (column, meta_uid, alltableschema) {
  let rtn = {}
  switch (column.ui_type) {
    case 'Select':
      rtn = getComponent('SelectInput')
      rtn.config.other = {
        isMulti: false,
        dataSource: getDataSourceSettings()
      }
      rtn.config.other.dataSource.MetaPopSettings.table = meta_uid
      rtn.config.other.dataSource.MetaPopSettings.column = column.column_name
      break
    case 'Switch':
      rtn = getComponent('SwitchInput')
      rtn.config.other = {
        isMulti: false,
        dataSource: getDataSourceSettings()
      }
      break
    case 'MultiSelect':
      rtn = getComponent('SelectInput')
      rtn.config.other = {
        isMulti: true,
        dataSource: getDataSourceSettings()
      }
      rtn.config.other.dataSource.MetaPopSettings.table = meta_uid
      rtn.config.other.dataSource.MetaPopSettings.column = column.column_name
      break
    case 'RadioButton':
      rtn = getComponent('RadioInput')
      rtn.config.other = {
        dataSource: getDataSourceSettings()
      }
      rtn.config.other.dataSource.MetaPopSettings.table = meta_uid
      rtn.config.other.dataSource.MetaPopSettings.column = column.column_name
      break
    case 'CalendarDate':
      rtn = getComponent('DatePicker')
      rtn.config.other.format = 'yyyy-MM-dd'
      break
    case 'Calendar':
      rtn = getComponent('DateTimePicker')
      rtn.config.other.format = 'yyyy-MM-dd HH:mm:ss'
      break
    case 'CalendarYear':
      rtn = getComponent('YearPicker')
      break
    case 'CalendarYearMonth':
      rtn = getComponent('MonthPicker')
      rtn.config.other.format = 'yyyy-MM'
      break
    case 'IntInput':
      rtn = getComponent('NumberInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        precision: 0,
        step: 1
      }
      break
    case 'Money':
      rtn = getComponent('NumberInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        precision: column.scale,
        step: 1
      }
      break
    case 'DecimalInput':
      rtn = getComponent('NumberInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        precision: column.scale,
        step: 1
      }
      break
    case 'TextArea':
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        type: 'textarea'
      }
      break
    case 'ReadonlyInput':
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: false,
        isReadOnly: true
      }
      break
    case 'EmailInput':
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        regExpress: '^[A-Za-z0-9\u4e00-\u9fa5]+@[a-zA-Z0-9_-]+(\\.[a-zA-Z0-9_-]+)+$',
        regCheckErr: '请输入正确的Email地址'
      }
      break
    case 'MobileInput':
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        regExpress: '^[1][3,4,5,7,8][0-9]{9}$',
        regCheckErr: '请输入正确的手机号'
      }
      break
    case 'MACInput':
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        regExpress: '[A-Fa-f0-9]{2}:[A-Fa-f0-9]{2}:[A-Fa-f0-9]{2}:[A-Fa-f0-9]{2}:[A-Fa-f0-9]{2}:[A-Fa-f0-9]{2}',
        regCheckErr: '请输入正确的MAC地址'
      }
      break
    case 'IDInput':
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        regExpress: '^[1-9]\\d{5}(18|19|([23]\\d))\\d{2}((0[1-9])|(10|11|12))(([0-2][1-9])|10|20|30|31)\\d{3}[0-9Xx]$',
        regCheckErr: '请输入正确的身份证号'
      }
      break
    case 'Picture':
      rtn = getComponent('PictureUpload')
      break
    case 'Pictures':
      rtn = getComponent('PicturesUpload')
      break
    case 'File':
      rtn = getComponent('FileUpload')
      break
    case 'Files':
      rtn = getComponent('FilesUpload')
      break
    case 'CascadeSelectMS':
      rtn = getComponent('CadecaseSelectInput')
      rtn.config.other = {
        separator: '/',
        cadecaseCategory: 'ms',
        isMulti: false,
        dataSource: {
          category: 'remote',
          MetaPopSettings: {
            table: meta_uid,
            orderList: [],
            column: column.column_name,
            startLevel: {
              table: '',
              column: '',
              filterValue: ''
            }
          }
        }
      }
      break
    case 'CascadeSelectTree':
      rtn = getComponent('CadecaseSelectInput')
      rtn.config.other = {
        separator: '/',
        cadecaseCategory: 'tree',
        isMulti: false,
        dataSource: {
          category: 'remote',
          MetaPopSettings: {
            table: meta_uid,
            orderList: [],
            column: column.column_name,
            startLevel: {
              table: '',
              column: '',
              filterValue: ''
            }
          }
        }
      }
      break
    case 'Multi_CascadeSelectMS':
      rtn = getComponent('CadecaseSelectInput')
      rtn.config.other = {
        separator: '/',
        cadecaseCategory: 'ms',
        isMulti: true,
        dataSource: {
          category: 'remote',
          MetaPopSettings: {
            table: meta_uid,
            orderList: [],
            column: column.column_name,
            startLevel: {
              table: '',
              column: '',
              filterValue: ''
            }
          }
        }
      }
      break
    case 'Multi_CascadeSelectTree':
      rtn = getComponent('CadecaseSelectInput')
      rtn.config.other = {
        separator: '/',
        cadecaseCategory: 'tree',
        isMulti: true,
        dataSource: {
          category: 'remote',
          MetaPopSettings: {
            table: meta_uid,
            orderList: [],
            column: column.column_name,
            startLevel: {
              table: '',
              column: '',
              filterValue: ''
            }
          }
        }
      }
      break
    case 'Pop':
      rtn = getComponent('PopInput')
      rtn.config.other = {
        isFilterDeleted: true,
        isMulti: false,
        query: {
          useDefault: true,
          conditions: [],
          filterColumns: []
        },
        table: {
          height: '',
          metaUid: '',
          columns: []
        },
        dataSource: {
          category: 'remote',
          remoteCategory: 'MetaPop',
          MetaPopSettings: {
            table: meta_uid,
            column: column.column_name,
            orderList: [],
            filterList: [],
            valueKey: '',
            labelKey: ''
          }
        }
      }
      rtn = setComponentConfig4Pop(rtn, column, alltableschema)
      break
    case 'MultiPop':
      rtn = getComponent('PopInput')
      rtn.config.other = {
        isFilterDeleted: true,
        isMulti: true,
        query: {
          useDefault: true,
          conditions: [],
          filterColumns: []
        },
        table: {
          height: '',
          metaUid: '',
          columns: []
        },
        dataSource: {
          category: 'remote',
          remoteCategory: 'MetaPop',
          MetaPopSettings: {
            table: meta_uid,
            column: column.column_name,
            orderList: [],
            filterList: [],
            valueKey: '',
            labelKey: ''
          }
        }
      }
      rtn = setComponentConfig4Pop(rtn, column, alltableschema)
      break
    case 'MapXY':
      rtn = getComponent('MapInput')
      break
    case 'MD':
      rtn = getComponent('MDInput')
      break
    default:
      rtn = getComponent('TextInput')
      rtn.config.other = {
        placeholder: '请输入',
        clearable: true,
        maxLength: column.precision
      }
      break
  }
  rtn.config.uid = Date.parse(new Date()) + '_' + Math.ceil(Math.random() * 999999)
  rtn.config.dataKey = column.column_name
  rtn.config.label = column.column_desc
  rtn.config.showLabel = true
  rtn.config.isRequired = !column.is_allow_empty
  return rtn
}
/**
 * 根据元数据栏位信息生成对应的Table栏位显示组件
 * @param {*} column 元数据栏位信息对象
 * @returns {
 *  isComponent: '是否为组件'
 *  component: '组件信息'
 * }
 */
export function getTableColumnViewerByMetaColumnInfo (column) {
  return getTableColumnViewerByName(getComponentNameByUIType(column.ui_type))
}
/**
 * 根据componentName生成对应的Table栏位显示组件
 * @param {object} name 组件名称
 * @returns {
 *  isComponent: '是否为组件'
 *  component: '组件信息'
 * }
 */
export function getTableColumnViewerByName (name) {
  let rtn = {
    isComponent: false,
    component: null
  }
  switch (name) {
    case 'PictureUpload':
      rtn.isComponent = true
      rtn.component = getComponent('PictureUpload')
      rtn.component.config.isEnable = false
      rtn.component.config.showLabel = false
      rtn.component.config.myStyle = {
        width: '48px',
        height: '48px'
      }
      break
    case 'PicturesUpload':
      rtn.isComponent = true
      rtn.component = getComponent('PicturesUpload')
      rtn.component.config.isEnable = false
      rtn.component.config.showLabel = false
      rtn.component.config.myStyle = {
        width: '48px',
        height: '48px'
      }
      break
    case 'FileUpload':
      rtn.isComponent = true
      rtn.component = getComponent('FileUpload')
      rtn.component.config.isEnable = false
      rtn.component.config.showLabel = false
      break
    case 'FilesUpload':
      rtn.isComponent = true
      rtn.component = getComponent('FilesUpload')
      rtn.component.config.isEnable = false
      rtn.component.config.showLabel = false
      break
    case 'MapInput':
      rtn.isComponent = true
      rtn.component = getComponent('MapInput')
      rtn.component.config.isEnable = false
      rtn.component.config.showLabel = false
      break
    case 'MDInput':
      rtn.isComponent = true
      rtn.component = getComponent('MDInput')
      rtn.component.config.isEnable = false
      rtn.component.config.showLabel = false
      break
    default:
      break
  }
  return rtn
}
/**
 * 根据元数据栏位信息获取表单的校验规则
 * @param {object} column 元数据栏位信息对象
 */
export function getFormRuleByMetaColumnInfo (column) {
  let rule = {
    name: column.column_name,
    required: !column.is_allow_empty,
    trigger: 'blur',
    dataType: 'string',
    pattern: '',
    message: column.column_desc + '不可为空'
  }
  switch (column.ui_type) {
    case 'RadioButton':
      rule.trigger = 'change'
      break
    case 'Select':
      rule.trigger = 'change'
      break
    case 'Switch':
      rule.trigger = 'change'
      break
    case 'MultiSelect':
      rule.trigger = 'change'
      rule.dataType = 'array'
      break
    case 'CheckBox':
      rule.trigger = 'change'
      rule.dataType = 'array'
      break
    case 'CalendarDate':
      rule.trigger = 'blur'
      rule.dataType = 'date'
      break
    case 'Calendar':
      rule.trigger = 'blur'
      rule.dataType = 'date'
      break
    default:
      break
  }
  return rule
}
